/*  Symbol数据类型 */
const { log } = console
// 1. 概述
let f1 = () => {
  // 1-1 声明Symbol类型的变量
  let sym1 = Symbol()
  let sym2 = Symbol()
  log(sym1 === sym2) // false
  // 1-2 声明变量指定描述
  sym1 = Symbol('foo')
  sym2 = Symbol('foo')
  log(sym1 === sym2) // false
  // 1-3 使用Symbol.for('')声明变量
  sym1 = Symbol.for('foo')
  sym2 = Symbol.for('foo')
  log(sym1 === sym2) // true
  // 1-4 获得描述器
  let desc = sym1.description
  log(desc) // foo
  sym2 = Symbol.for('abc')
  let desc1 = Symbol.keyFor(sym2)
  log(desc1) // abc
}

// 2. 对象属性使用的Symbol变量
let f2 = () => {
  let obj = {
    foo: 'hello',
  }
  let sym = Symbol('boo')
  obj[sym] = 'run'
  log(obj) // { foo: 'hello', [Symbol(boo)]: 'run' }
  // 取出属性
  let rt = obj[sym]
  log(rt) // 'run'
}
// f2()

// 3. 内置的 Symbol 值 Symbol.iterator
let f3 = () => {
  // 对象的Symbol.iterator属性，指向该对象的默认遍历器方法。
  let obj = {
    id: 1,
    name: 'tom',
    age: 20,
    // 对象部署迭代器后可以使用for-of遍历对象的属性值
    [Symbol.iterator]: function () {
      let index = 0
      const self = this
      let keys = Object.keys(self)
      return {
        next() {
          if (index < keys.length) {
            return { value: { k: keys[index], v: self[keys[index++]] }, done: false }
          } else {
            return { value: null, done: true }
          }
        },
      }
    },
  }
  // 获得对象的迭代器
  let iterator = obj[Symbol.iterator]()
  // log(iterator.next())
  // log(iterator.next())
  // log(iterator.next())
  // log(iterator.next())
  for (let item of obj) {
    log(item)
  }
}
f3()
